﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace HirelSeriesH.Tools
{
    class CheckWorker
    {
        public static byte PowerCommandsADD(byte[] command)
        {
            int sum = 0;
            for (int i = 0; i < command.Length - 1; i++)
            {
                sum += command[i];
            }
            sum = sum % 65535;
            return (byte)(sum & 0xff);
        }
        public static bool CheckModbusCRC16(byte[] bytes)
        {
            bool r;
            if (bytes.Length < 4)
            {
                r = false;
            }
            else
            {
                byte[] data = new byte[bytes.Length - 2];
                byte[] dataCrC = new byte[2];
                for (int i = 0; i < bytes.Length - 2; i++)
                {
                    data[i] = bytes[i];

                }
                dataCrC[0] = bytes[bytes.Length - 2];
                dataCrC[1] = bytes[bytes.Length - 1];

                byte[] checkedData = ModbusCRC16(data);
                if ((checkedData[checkedData.Length - 2] == dataCrC[0]) && (checkedData[checkedData.Length - 1] == dataCrC[1]))
                {
                    r = true;
                }
                else
                {
                    r = false;
                }
            }
            return r;
        }

        public static byte[] ModbusCRC16(byte[] bytes)
        {
            byte[] crc = CRC16ForLowHigh(bytes);
            byte[] result = new byte[bytes.Length + crc.Length];
            bytes.CopyTo(result, 0);
            crc.CopyTo(result, bytes.Length);
            return result;
        }

        public static byte[] ADD(byte[] bytes, bool isTest)
        {
            byte sum = checkSum(bytes);
            if (sum == 0XAA && isTest)
            {
                sum = 0X55;
            }
            byte[] result = new byte[bytes.Length + 1];
            bytes.CopyTo(result, 0);
            result[result.Length - 1] = sum;
            return result;
        }
        public static byte[] CRC16ForLowHigh(byte[] bytes)
        {
            int length = bytes.Length;
            if (length > 0)
            {
                ushort crc = 0xFFFF;
                for (int i = 0; i < length; i++)
                {
                    crc = (ushort)(crc ^ bytes[i]);
                    for (int j = 0; j < 8; j++)
                    {
                        if ((crc & 1) != 0)
                        {
                            crc = (ushort)((crc >> 1) ^ 0xA001);
                        }
                        else
                        {
                            crc = (ushort)(crc >> 1);
                        }
                    }
                }
                byte high_order = (byte)((crc & 0xFF00) >> 8);
                byte Low_order = (byte)(crc & 0x00FF);

                return new byte[] { Low_order, high_order };
            }
            return new byte[] { 0x00, 0x00 };
        }

        public static byte[] CRC16ForHighLow(byte[] bytes)
        {
            int length = bytes.Length;
            if (length > 0)
            {
                ushort crc = 0xFFFF;
                for (int i = 0; i < length; i++)
                {
                    crc = (ushort)(crc ^ bytes[i]);
                    for (int j = 0; j < 8; j++)
                    {
                        if ((crc & 1) != 0)
                        {
                            crc = (ushort)((crc >> 1) ^ 0xA001);
                        }
                        else
                        {
                            crc = (ushort)(crc >> 1);
                        }
                    }
                }
                byte high_order = (byte)((crc & 0xFF00) >> 8);
                byte Low_order = (byte)(crc & 0x00FF);

                return new byte[] { high_order, Low_order };
            }
            return new byte[] { 0x00, 0x00 };
        }

        public static byte checkSum(byte[] data)
        {
            int sum = 0;
            for (int i = 0; i < data.Length; i++)
            {
                sum += data[i];
            }
            sum = sum % 65535;
            return (byte)(sum & 0xff);
        }

        public static bool checkSum(byte[] data,byte sumInput)
        {
            int sum = 0;
            for (int i = 0; i < data.Length - 1; i++)
            {
                sum += data[i];
            }
            sum = sum % 65535;

            if(sumInput == 85 && ((byte)(sum & 0xff)) == 170)
            {
                return true;
            }
            return ((byte)(sum & 0xff)).ToString("X2") == sumInput.ToString("X2");
        }

        /// <summary>
        /// 字节数组转字符串
        /// </summary>
        /// <param name="bytes"></param>
        /// <returns></returns>
        public static string byteToHexStr(byte[] bytes)
        {
            string returnStr = "";
            if (bytes != null)
            {
                for (int i = 0; i < bytes.Length; i++)
                {
                    returnStr += bytes[i].ToString("X2");
                }
            }
            return returnStr;
        }

    }
}
